package com.ler.yrmall.product.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.lang.Assert;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ler.yrmall.coupon.api.CouponApi;
import com.ler.yrmall.coupon.dto.SeckillSkuDTO;
import com.ler.yrmall.product.form.SkuForm;
import com.ler.yrmall.search.api.SearchApi;
import com.ler.yrmall.basic.Form;
import com.ler.yrmall.basic.Result;
import com.ler.yrmall.enums.ErrorCodeEnum;
import com.ler.yrmall.exception.BusinessException;
import com.ler.yrmall.product.entity.SkuEntity;
import com.ler.yrmall.product.entity.SpuAttrValueEntity;
import com.ler.yrmall.product.mapper.SkuInfoMapper;
import com.ler.yrmall.product.service.SkuAttrValueService;
import com.ler.yrmall.product.service.SkuService;
import com.ler.yrmall.product.service.SpuAttrValueService;
import com.ler.yrmall.product.vo.SkuVO;
import com.ler.yrmall.product.vo.SpuSaleMinPriceVO;
import org.apache.dubbo.config.annotation.DubboReference;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.Collections;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @author leron
 */
@Service
public class SkuServiceImpl extends ServiceImpl<SkuInfoMapper, SkuEntity> implements SkuService {

    @Resource
    private SkuAttrValueService skuSaleAttrValueService;

    @Resource
    private SpuAttrValueService productAttrValueService;

    @Resource
    private SkuAttrValueService skuAttrValueService;

    @DubboReference
    private CouponApi couponApi;

    @Resource
    private SearchApi searchApi;


    @Override
    public List<SkuVO> listSkuBySpuId(Long spuId) {
        return this.baseMapper.listSkuBySpuId(spuId);
    }

    @Override
    public List<SkuEntity> list(Form request) {
        return this.list(Wrappers.<SkuEntity>lambdaQuery()
                .like(request.getKeyword() != null,SkuEntity::getName,request.getKeyword()));
    }

    @Override
    public Long getSpuIdBySkuId(Long skuId) {
        SkuEntity byId = this.getById(skuId);
        return byId.getSpuId();
    }

    @Override
    public List<SpuSaleMinPriceVO> computeSpuSaleAndMinPrice(List<Long> spuIds) {
        return this.baseMapper.computeSpuSaleAndMinPrice(spuIds);
    }

    @Override
    public SkuVO getSkuById(Long skuId) {
        SkuEntity entity = this.getById(skuId);
        List<String> attrs = skuSaleAttrValueService.getAttrsAsString(skuId);
        List<String> attrValues = skuSaleAttrValueService.getAttrValuesAsString(skuId);
        SkuVO skuInfoVO = BeanUtil.copyProperties(entity, SkuVO.class);
        skuInfoVO.setSkuAttrs(attrs);
        skuInfoVO.setAttrValues(attrValues);
        // 秒杀信息
        Result<SeckillSkuDTO> result = couponApi.getSkuSeckill(skuId);
        SeckillSkuDTO data = result.getData();
        if (data != null) {
            SkuVO.SeckillInfoVO dto = new SkuVO.SeckillInfoVO();
            dto.setPrice(data.getPrice());
            dto.setSeckillId(data.getSeckillId());
            dto.setRandomCode(data.getRandomCode());
            dto.setEndTime(data.getEndTime());
            skuInfoVO.setSeckillInfo(dto);
        }
        return skuInfoVO;
    }

    @Override
    public IPage<SkuVO> pageGroupBySpuId(SkuForm form) {
        IPage<SkuVO> skuInfos = this.baseMapper.pageGroupBySpuId(form.getPage(),form);
        if (skuInfos.getRecords().size() == 0) {
            return skuInfos;
        }
        List<Long> spuIds = skuInfos.getRecords().stream().map(SkuVO::getSpuId).collect(Collectors.toList());
        List<SpuAttrValueEntity> quickAttrs =  productAttrValueService.getQuickShowAttr(spuIds);
        skuInfos.getRecords().forEach(item -> {
            List<List<String>> quickAttr = quickAttrs.stream()
                    .filter(e -> item.getSpuId().equals(e.getSpuId()))
                    .map(SpuAttrValueEntity::getAttrValue)
                    .collect(Collectors.toList());
            item.setQuickShowAttr(quickAttr.stream().flatMap(List::stream).collect(Collectors.toList()));
        });
        return skuInfos;
    }

    @Override
    public void deleteBySpuId(long spuId) {
        this.remove(Wrappers.<SkuEntity>lambdaQuery().eq(SkuEntity::getSpuId,spuId));
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteSku(Long id) {
        // 删除 sku-attr
        skuAttrValueService.deleteBySkus(Collections.singletonList(id));
        Result<Boolean> result = searchApi.deleteSku(Collections.singletonList(id));
        Assert.isTrue(result.isSuccess() && !result.getData(),() -> new BusinessException(ErrorCodeEnum.ES_DELETE_ERROR));
        this.removeById(id);
    }
}